from django.shortcuts import render
from rest_framework.generics import GenericAPIView,CreateAPIView,RetrieveAPIView,UpdateAPIView
from rest_framework.response import Response
from rest_framework.views import APIView
from random import randint
# Create your views here.
from django_redis import get_redis_connection

from carts.utils import merge_cart_cookie_to_redis
from meiduo_mall.libs.yuntongxun.sms import CCP
from celery_tasks.sms.tasks import send_sms_code
from .models import User
from .serializers import UserSerizlizer,UserDetailSerializer,UserEmailSerializer,VerifyEmailSerializer
from rest_framework.permissions import IsAuthenticated
from itsdangerous import TimedJSONWebSignatureSerializer as TJS
from django.conf import settings
from rest_framework import status
from rest_framework_jwt.views import ObtainJSONWebToken
"""
1.先在url正则匹配mobile，验证mobile格式
2.使用随机数生成短信验证码
3.先与reids建立链接，保存短信验证码到redis中
4.使用云通讯发送短信验证码
5.返回值ＯＫ
6.判断60秒内不能再登录
"""
# get  /sms_codes/mobile  ok
class SMSCodeView(APIView):
    def get(self,request,mobile):

        # 60秒内不能再次请求
        conn = get_redis_connection('verify')
        flag = conn.get('sms_flag')
        if flag:
            return Response({'message':'error'},status=400)

        # 生成短信验证码
        sms_code = '%06d'%randint(0,999999)
        print('sms_code:',sms_code)

        #　验证码保存到redis中
            # 每个缓存都有个名字，指定链接哪个缓存
            # 存储到缓存

        # 建立管道对象
        p1 = conn.pipeline()
        p1.setex('SMScode_%s'%mobile,300,sms_code)
        p1.setex('sms_flag', 60, 1)
        # 建立链接，p1发送数据到redis
        p1.execute()

        # 发送短信
        # ccp = CCP()
        # ccp.send_template_sms('13427415130',[sms_code,5],1)

        send_sms_code.delay(mobile,sms_code)

        # 返回值处理
        return Response({'message':'ok'})


# get usernames/name username,count

# 主要查询用户数量，不用判断，返回数据给前端判断
class UserNameView(APIView):

    def get(self,request,name):

        # 查询用户数量
        try:
            count = User.objects.filter(username=name).count()
        except Exception as e:
            return Response({'message':'查询用户数量异常'})

        # 返回值处理
        return Response({'username':name,'count':count})


# get mobiles/mobile  mobile,count

class MobileView(APIView):

    def get(self,request,mobile):

        # 查询手机号数量

        count = User.objects.filter(mobile=mobile).count()

        # 返回值处理
        return Response({'mobile':mobile,'count':count})


# post  /users/  username,password,password2,sms_code,mobile,allow
class UserView(CreateAPIView):
    serializer_class = UserSerizlizer
    # 查询数据库返回对象或查询集　传给序列化时使用
    # queryset = User.objects.all()

    # 保存指定字段的值到数据库，不需要保存的就在验证函数时删除，
    # 如果其他函数想要调用传指定的字段需要在验证函数删除指定字段
    # def post(self,request):

        # 接收数据

        # 验证短信验证码是否正确

        # 保存数据

        # 返回数据


class UserDetailView(RetrieveAPIView):
    serializer_class = UserDetailSerializer
    # queryset = User.objects.all()
    permission_classes = [IsAuthenticated]
    # get  user/  id,email,username,mobile,email_active
    # def get(self,request):
    def get_object(self):
        # 通过前端传过来的token值解密得出user对象给request
        # view函数把request对象赋值给了self.request实例对象
        user = self.request.user
        return user


class UserEmailView(UpdateAPIView):
    serializer_class = UserEmailSerializer
    # put email/  email  id,email
    # def put(self,request):
    #     serializer = UserEmailSerializer(instance=request.user,data=request.data,context={'user':request.user})
    #     serializer.is_valid(raise_exception=True)
    #     serializer.save(user=requesr.user)
    #     return Response(serializer.data)
    def get_object(self):
        return self.request.user



class VerifyEmailView(GenericAPIView):
    serializer_class = VerifyEmailSerializer

    # get /email/verification/?token=xxx token  message
    def get(self,request):
        # 接受参数
        # query_params是一个字典
        data = request.query_params
        if data is None:
            return Response({'message':'缺少token'},status=status.HTTP_400_BAD_REQUEST)

        # 验证解密token
        serialzier = self.get_serializer(data=data)

        serialzier.is_valid(raise_exception=True)

        data = serialzier.validated_data['data']

        # 更新用户的email_active值
        try:
            user = User.objects.get(id=data['id'],username=data['username'])
        except:
            return Response({'message':'用户不存在'},status=status.HTTP_400_BAD_REQUEST)

        user.email_active = True
        user.save()

        return Response({'message':'ok'},status=status.HTTP_200_OK)

class UserAuthorizeView(ObtainJSONWebToken):

    def post(self, request, *args, **kwargs):
        response = super().post(request, *args, **kwargs)

        # 仿照drf jwt扩展对于用户登录的认证方式，判断用户是否认证登录成功
        # 如果用户登录认证成功，则合并购物车
        serializer = self.get_serializer(data=request.data)

        if serializer.is_valid():
            user = serializer.validated_data.get('user')
            response = merge_cart_cookie_to_redis(request, user, response)

        return response